package net

import (
	"../state"
	"net/rpc"
)

const (
	rpcPoolSize = 10
)

var (
	udpInstance *NetUDP
	RpcInstance *NetTCP
)

type NetPacket struct {
	Addr string
	Body []byte
}

func PacketSend(msg interface{}, addr string) {
	udpInstance.Send(msg, addr)
}

func PeersSend(msg interface{}) {
	for _, v := range state.Peers {
		udpInstance.Send(msg, v.Addr+":"+v.Port)
	}
}

func PeerSend(hostid string, msg interface{}) {
	for _, v := range state.Peers {

		if v.Id != hostid {
			continue
		}

		udpInstance.Send(msg, v.Addr+":"+v.Port)
		break
	}
}

func InitializeUDP(port string, fn NetUDPEventHandler) error {

	//
	udpInstance = &NetUDP{
		in:       make(chan *NetPacket, 100000),
		out:      make(chan *NetPacket, 100000),
		handlers: make([]NetUDPEventHandler, 0, 4),
	}

	err := udpInstance.ListenAndServe(port, fn)
	if err != nil {
		return err
	}

	return nil
}

func InitializeRpc() (*NetTCP, error) {

	//
	RpcInstance = &NetTCP{
		out:      make(chan *NetCall, 30000),
		poolsize: rpcPoolSize,
		pool:     make(chan *rpc.Client, rpcPoolSize),
	}

	for i := 0; i < rpcPoolSize; i++ {
		RpcInstance.pool <- nil
	}

	go RpcInstance.sending()

	return RpcInstance, nil
}
